"use strict";

const Service = require("egg").Service;

class SysUserService extends Service {

  // 获取用户信息与公司
  async checkUserCanLogin(params) {
    try {
      const { Op } = this.app.Sequelize;
      const query = {
        where: {
          delFlag: false,
          [Op.or]: [
            {
              username: params.username,
            },
            {
              mobile: params.username,
            },
            {
              email: params.username
            }
          ],
        },
        attributes: ['id', 'username', 'password', 'mobile', 'email', 'status', 'userType', 'loginIp'],
      };
      const res = await this.ctx.model.SysUser.findOne(query);
      if (!res) throw '查询不到对应登录主体，请检查账号是否填写正确';
      return this.ctx.helper.ormSuccess(res);
    } catch (err) {
      return this.ctx.helper.ormError(err);
    }
  }

  // 获取用户信息
  async getUserInfo(id) {
    try {
      const { Op } = this.app.Sequelize;
      const query = {
        where: {
          delFlag: false,
          id
        },
        attributes: {
          exclude: ['password', 'createById', 'delFlag']
        },
        include: [{
          // 查询用户关联角色
          model: this.ctx.model.SysRole,
          as: "role",
          required: false, // 左连接非必须
          where: {
            delFlag: false,
          },
          attributes: ["id", "roleName", "roleKey", "status"],
          include: [
            // 查询角色关联菜单
            {
              model: this.ctx.model.SysMenu,
              as: "menu",
              required: false,
              where: {
                status: true,
              },
              attributes: {
              },
            },
          ],
          order: [["menu", "sort", "ASC"]], // 菜单按sort排序
        },]
      }
      const userRes = await this.ctx.model.SysUser.findOne(query);
      const user = userRes ? this.ctx.helper.deepCopy(userRes) : null;
      if (!user) throw "用户不存在";
      return this.ctx.helper.ormSuccess(user);
    } catch (err) {
      return this.ctx.helper.ormError(err);
    }
  }

  // 分页查询
  async page(params) {
    try {
      //拿到Op进行数据库的操作
      const { Op } = this.app.Sequelize;
      //得到页码偏移量  (pi默认值为1 ps默认值为100)
      const offset = (Number(params.pi || 1) - 1) * Number(params.ps || 100);
      //建立查询的基本参数(未删除)
      let queryCriteria = {
        delFlag: false,
      };
      //如果状态为1,表示为启动状态
      if (this.ctx.helper.isDef(params.status)) {
        queryCriteria = {
          ...queryCriteria,
          status: params.status,
        };
      }
      //如果有关键字
      if (this.ctx.helper.isDef(params.keyword)) {
        queryCriteria = {
          ...queryCriteria,
          [Op.or]: [
            { username: { [Op.like]: `%${params.keyword}%` } },
            { nickname: { [Op.like]: `%${params.keyword}%` } },
            { mobile: { [Op.like]: `%${params.keyword}%` } },
            { email: { [Op.like]: `%${params.keyword}%` } },
          ],
        };
      }
      let query = {
        limit: Number(params.ps || 100),
        offset,
        distinct: true, //这一句可以去重，它返回的 count 不会把你的 include 的数量算进去
        where: queryCriteria,
        attributes: { exclude: ["delFlag"] }, //返回除了delFlag的其他所有参数
      };

      query.include = [
        {
          model: this.ctx.model.SysRole,
          as: "role",
          required: false, // 左连接非必须
          where: {
            delFlag: false,
          },
          attributes: ["id", "roleName", "roleKey", "status"],
        }
      ]
      const res = await this.ctx.model.SysUser.findAndCountAll(query);
      return this.ctx.helper.ormSuccess(res);
    } catch (err) {
      return this.ctx.helper.ormError(err);
    }
  }


  // 创建
  async create(params) {
    try {
      const { Op } = this.app.Sequelize;
      let query = {
        where: {
          delFlag: false,
          [Op.or]: [
            {
              username: params.username,
            },
            {
              mobile: params.mobile,
            },
          ],
        },
      };
      if (params.email) {
        query.where[Op.or].push({ email: params.email })
      }
      //查看是否已经有了用户名或手机号或邮箱有重复的?
      const existData = await this.ctx.model.SysUser.findOne(query);
      if (existData) {
        if (existData.username === params.username) throw "用户名已被使用";
        if (existData.mobile === params.mobile) throw "手机号已被使用";
        if (existData.email === params.email) throw "邮箱已被使用";
      }
      //使用model层的创建用户
      await this.ctx.model.SysUser.create(params);
      return this.ctx.helper.ormSuccess()
    } catch (err) {
      return this.ctx.helper.ormError(err);
    }
  }

  // 更新
  async edit(id, params) {
    try {
      const { Op } = this.app.Sequelize;
      const updateObj = await this.ctx.model.SysUser.findByPk(id);
      if (!updateObj) throw "查询不到该账号";
      //如果参数中有要修改的手机号或者是邮箱号,则先查询一下是否有和params下相同的属性值,如果有,则抛出错误,如果没有,则继续.
      if (params.mobile || params.email) {
        let query = {
          where: {
            delFlag: false,
            id: {
              [Op.not]: id
            },
            [Op.or]: [],
          },
        };
        if (params.mobile) {
          query.where[Op.or].push({ mobile: params.mobile })
        }
        if (params.email) {
          query.where[Op.or].push({ email: params.email })
        }
        const existData = await this.ctx.model.SysUser.findOne(query);
        if (existData) {
          if (params.mobile && existData.mobile === params.mobile) throw '手机号已被使用';
          if (params.email && existData.email === params.email) throw '邮箱已被使用';
        }
      }
      const res = await updateObj.update(params);
      return this.ctx.helper.ormSuccess(this.ctx.helper.deepCopy(res));
    } catch (err) {
      return this.ctx.helper.ormError(err);
    }
  }

  /**
   * @description 删除（逻辑删除）
   * @param {*} id 
   * @returns 
   */
  async del(id) {
    try {
      if (Number(id) === 1) throw '系统超级管理员账号，不允许删除';
      const entity = await this.ctx.model.SysUser.findByPk(id);
      if (!entity) throw '账号不存在';

      //只进行软件删除
      await entity.update({
        delFlag: true
      });
      return this.ctx.helper.ormSuccess();
    } catch (err) {
      return this.ctx.helper.ormError(err);
    }
  }


  /**
   * 查找是否有该用户，并修改该用户的信息。
   * @param {参数类型} 参数名 - 参数描述
   * @returns {返回值类型} 返回值描述
   */
  async updatePassword(param) {
    try {
      const userId = param.userId
      
      // 查找是否存在该用户
      const user = await this.ctx.model.SysUser.findOne({
        where: {
          id: userId
        }
      });

      if (!user) {
        throw '该用户不存在';
      }

      // 更新用户密码
      user.password = param.password;
      await user.save();

      return this.ctx.helper.ormSuccess({});
    } catch (err) {
      return this.ctx.helper.ormError(err);
    }
  }

  /**
   * @description 获取系统账号绑定的角色ID
   * @param {*} userId 
   * @returns 
   */
  async getRoleIdByUser(userId) {
    try {
      const _res = await this.ctx.model.SysUserRole.findAll({
        where: {
          userId
        }
      })
      const res = this.ctx.helper.deepCopy(_res);
      const roleIds = res.map(item => item.roleId);
      return this.ctx.helper.ormSuccess(roleIds)
    } catch (err) {
      return this.ctx.helper.ormError(err);
    }
  }


  // 更新用户角色
  async updateRole(userId, params) {
    const transaction = await this.ctx.model.transaction();
    try {
      // 先删除关联表中的数据
      await this.ctx.model.SysUserRole.destroy({
        where: {
          userId
        }
      })
      // 批量插入新的关联关系
      if (Array.isArray(params) && params.length > 0) {
        await this.ctx.model.SysUserRole.bulkCreate(params, { updateOnDuplicate: ["userId", "roleId"] })
      }

      //如果成功就插入
      await transaction.commit();
      return this.ctx.helper.ormSuccess();
    } catch (err) {
      //如果失败就回滚
      await transaction.rollback();
      return this.ctx.helper.ormError(err);
    }
  }

}

module.exports = SysUserService;
